package com.polaris.live.im.sfs.processor.impl.system

import com.polaris.live.common.cacha.CacheUtil
import com.polaris.live.common.cacha.UserManager
import com.polaris.live.im.db.database.AppDatabase
import com.polaris.live.im.db.entity.MessageExcludeEntity
import com.polaris.live.im.manager.ImMessageManager
import com.polaris.live.im.sfs.core.SmartFoxConnector
import com.polaris.live.im.sfs.core.bean.DataArgument
import com.polaris.live.im.sfs.processor.AbstractMessageProcessor
import com.polaris.live.im.sfs.processor.InterruptMessageProcessSignal
import com.polaris.live.im.sfs.processor.MessageProcessSignal
import com.polaris.live.im.sfs.processor.ProceedMessageProcessSignal

/**
 * AbstractExcludeMessageProcessor
 *
 * @author Created by lucas on 2023/11/25 09:46
 */
abstract class AbstractExcludeMessageProcessor : AbstractMessageProcessor() {

    /**
     * 处理排除信号
     */
    protected suspend fun exclude(
        type: Int,
        argument: DataArgument,
        proceed: (suspend () -> MessageProcessSignal)? = null
    ): MessageProcessSignal {
        val msgId = argument.getMsgId()
            ?: return if (proceed != null) {
                proceed()
            } else {
                ProceedMessageProcessSignal
            }

        return exclude(type, argument.command, msgId, argument.getSeqId(), proceed)
    }

    /**
     * 处理排除信号
     */
    protected suspend fun exclude(
        type: Int,
        command: String,
        msgId: String,
        seqId: Long? = null,
        proceed: (suspend () -> MessageProcessSignal)? = null
    ): MessageProcessSignal {
        //已经存在中断处理
        val userId = UserManager.getUserId()
        return if (AppDatabase.instance.messageExcludeDao().existsByMsgId(userId, msgId)) {
            //本地已经存在的消息最好ack，告知服务端消息已经处理，不需要再发送
            if (type == SmartFoxConnector.CLIENT_CHAT && seqId != null) {
                ImMessageManager.ackMessage(command, seqId)
            }

            InterruptMessageProcessSignal
        } else {
            AppDatabase.instance.messageExcludeDao()
                .insert(MessageExcludeEntity(null, userId, msgId, CacheUtil.getServerTime()))

            if (proceed != null) {
                proceed()
            } else {
                ProceedMessageProcessSignal
            }
        }
    }
}